package com.atugigu.controller;

import com.atugigu.pojo.User;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.servlet.ModelAndView;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

/**
 * @author ：HB
 * @date ：Created in 2020/10/29 10:04
 * @description：
 * 测试页面跳转的controller:
 * 1. 直接返回字符串
 * 2. 通过ModelAndView对象返回
 *
 * \ @RestController = @Controller + @ResponseBody，
 * 表明该Controller类所有的方法都返回JSON格式的数据(没有加@RequestMapping注解的方法除外)。
 *
 * 加入@ResponseBody注解就能返回JSON格式数据的原因是：
 * SpringMVC提供的HttpMessageConverter自动转为JSON ，
 * 如果使用了Jackson或者Gson，不需要额外配置就可以自动返回JSON了，
 * 因为框架帮我们提供了对应的HttpMessageConverter ，如果使用了Alibaba的Fastjson的话，
 * 则需要自己手动提供一个相应的 HttpMessageConverter的实例。
 */


@Controller
@RequestMapping("/user")
public class UserController {

    /**
     * 测试返回值是String
     *测试：http://localhost:8080/springmvc_day02_01_response/user/testString
     * @param model
     * @return
     */
    @RequestMapping("/testString")
    public String testString(Model model) {
        System.out.println("testString方法执行了...");
        // 模拟从数据库中查询出User对象
        User user = new User();
        user.setUsername("美美");
        user.setPassword("123");
        user.setAge(30);
        // model对象
        model.addAttribute("user", user);
        //success 通过视图资源解析器进行解析 拼接
        return "success";
    }

    /**
     * 测试返回值是void
     * 请求转发一次请求，不用编写项目的名称
     * 测试：user/testVoid/
     */
    @RequestMapping("/testVoid")
    public void testVoid(HttpServletRequest request, HttpServletResponse response) throws Exception {
        // 设置中文乱码
        response.setCharacterEncoding("UTF-8");
        response.setContentType("text/html;charset=UTF-8");
//         System.out.println("testVoid方法执行了...");
        // 编写请求转发的程序
//          request.getRequestDispatcher("/WEB-INF/pages/success.jsp").forward(request,response);

        // 重定向
        response.sendRedirect(request.getContextPath() + "/index.jsp");
        return;
    }


    /**
     * Spring MVC 提供了以下几种途径输出模型数据：
     * ModelAndView: 处理方法返回值类型为 ModelAndView 时, 方法体即可通过该对象添加模型数据
     * Map 及 Model: 入参为 org.springframework.ui.Model、org.springframework.ui.ModelMap 或 java.uti.Map 时，处理方法返回时，Map 中的数据会自动添加到模型中。
     * //@SessionAttributes【了解】: 将模型中的某个属性暂存到 HttpSession 中，以便多个请求之间可以共享这个属性
     * //@ModelAttribute【原理深，了解】: 方法入参标注该注解后, 入参的对象就会放到数据模型中
     */

    /**
     * 测试返回modelandview
     * Model:模型 作用封装数据
     * View: 视图 作用展示数据
     * 测试：user/testModelAndView
     * 测试：http://localhost:8080/springmvc_day02_01_response/user/testModelAndView
     */
    @RequestMapping("/testModelAndView")
    public ModelAndView testModelAndView() {
        ModelAndView mav = new ModelAndView();
        User user = new User();
        user.setUsername("123");
        user.setPassword("123");
        user.setAge(18);
        //在域中添加数据
        //所以在success页面中可以访问到user
        mav.addObject("user", user);
        mav.setViewName("success");

        return mav;

    }

    /**
     * 改进版：可以不进行 ModelAndView mav = new ModelAndView();
     * 直接在参数中加入 ModelAndView
     * 因为springmvc对方法的参数 可以帮你进行响应的注入
     * 比如你在写ModelAndView参数时，在解析这个方法时，发现有一个ModelAndView 参数需要我注入，就自动帮你注入了
     *测试：http://localhost:8080/springmvc_day02_01_response/user/testModelAndView2
     * @return
     */
    @RequestMapping("/testModelAndView2")
    public ModelAndView testModelAndView2(ModelAndView mav) {
        User user = new User();
        user.setUsername("123");
        user.setPassword("123");
        user.setAge(18);
        //在域中添加数据
        //所以在success页面中可以访问到user
        mav.addObject("user", user);
        mav.setViewName("success");
        return mav;

    }

    /**
     * 用原始的方法往域中存放数据
     * 测试：http://localhost:8080/springmvc_day02_01_response/user/testOld
     */
    @RequestMapping("/testOld")
    public String testOld(HttpServletRequest request,HttpServletResponse response) {
        User user = new User();
        user.setUsername("123");
        user.setPassword("123");
        request.setAttribute("user",user);
        return "success";
    }
}
